package middleware

import (
	"crypto/md5"
	"demo/internal/errno"
	"demo/internal/service"
	"encoding/hex"
	"fmt"
	"sort"
	"strings"

	"github.com/gogf/gf/v2/encoding/gjson"
	"github.com/gogf/gf/v2/frame/g"
	"github.com/gogf/gf/v2/net/ghttp"
)

type sMiddleware struct{}

func init() {
	service.RegisterMiddleware(New())
}

func New() *sMiddleware {
	return &sMiddleware{}
}

func (s *sMiddleware) Auth(r *ghttp.Request) {

	token := r.Header.Get("Authorization")
	if token != "zyb123" {

		r.Response.WriteJson(g.Map{
			"code": errno.TokenError.Code,
			"msg":  errno.TokenError.Msg,
			"data": "",
		})
		r.ExitAll()
	}

	j, _ := r.GetJson()
	m, _ := gjson.LoadJson(j)
	mMap := m.Map()

	is_valid := validSignature(mMap, "cartierlepoard2022210")
	fmt.Println(is_valid)

	if is_valid == false {
		r.Response.WriteJson(g.Map{
			"code": errno.SignError.Code,
			"msg":  errno.SignError.Msg,
			"data": "",
		})
		r.ExitAll()
	}

	r.Middleware.Next()
}

func getType(v interface{}) string {
	// Get the type of the variable as a string
	return fmt.Sprintf("%T", v)
}

func validSignature(params map[string]interface{}, secretKey string) bool {
	var keys []string
	for k := range params {
		keys = append(keys, k)
	}
	sort.Strings(keys)

	// Concatenate the timestamp, sorted parameters, and secret key
	var data string
	for _, k := range keys {
		if params[k] != "" && k != "sign" {
			data += k + "=" + params[k].(string) + "&"
		}
	}

	// data1 := data[:len(data)-1]
	data += "key=" + secretKey

	// Calculate the MD5 hash of the concatenated data
	hash := md5.Sum([]byte(data))
	// Convert the hash to a hexadecimal string
	signature := strings.ToUpper(hex.EncodeToString(hash[:]))

	if params["sign"] == signature {
		return true
	}

	return false
}
